local NewRareInfoView = require("app.newBag.views.NewRareInfoView")
local NewBoxTipsView = require("app.newBag.views.NewBoxTipsView")
local UIUtil = {}

function UIUtil:showTips(triggerNode, data)
    local ft = nil
    local dataTemp = {
        name=data.name,
        string1 = data.desc1,
        string3 = data.desc2,
    }

    if self.eventTips then
        self.eventTips:setData( dataTemp )
    else
        self.eventTips = NewRareInfoView.create()
        self.eventTips:setData( dataTemp )
        self.mUINode:addChild( self.eventTips )

        -- 点击空白区域关闭
        display.nodeRemoveForNotHit(self.eventTips, function()
            if cc.isDead(self.eventTips) == false then
                self.eventTips:removeFromParent()
                self.eventTips = nil
            end
        end)
    end

    local triggerNodeBoundingBox = triggerNode:getBoundingBox()
    local worldPosTemp = triggerNode:getParent():convertToWorldSpace( cc.p( triggerNodeBoundingBox.x, triggerNodeBoundingBox.y ) )
    triggerNodeBoundingBox.x = worldPosTemp.x
    triggerNodeBoundingBox.y = worldPosTemp.y
    display.adjustNodePos( triggerNodeBoundingBox, self.eventTips )
end

function UIUtil:showBoxTipsView(triggerNode, dataTemp, distanceX)

    local rarePanel = NewBoxTipsView.create()
    rarePanel:setData(dataTemp)
    UIHandler:addPopupUi(rarePanel)

    -- 点击空白区域关闭
    display.nodeRemoveForNotHit(rarePanel, function()
        rarePanel:removeFromParent()
    end)

    local box = triggerNode:getBoundingBox()
    local worldPos = triggerNode:getParent():convertToWorldSpace(cc.p(box.x, box.y))
    box.x = worldPos.x
    box.y = worldPos.y
    display.adjustNodePos(box, rarePanel, distanceX)
end

local function ccall(f, ...)
    if f then
        f(...)
    end
end

function UIUtil:createTreeView(param)
    local tnodes = param.tnodes
    if #tnodes <= 0 then return end

    self.typeTree = param.treeList
    self.typeTree:setGravity(ccui.ListViewGravity.left)
    self.typeTree:setItemsMargin(0)

    self.treeData = param.root

    self.selColor = cc.c3b(255,225,132)
    self.idlColor = cc.c3b(172,165,154)
    
    local lastBtn = {}
    local lastLv3Btn = nil
    
    local lastBtn = {}
    local function checkLastBtn(n)
        while n and n.ndata do
            local last = lastBtn[n.ndata.lv]
            if last ~= n then
                if last then
                    last.checkAndColapse(false)
                end
                n.check(true)

                lastBtn[n.ndata.lv] = n
            end

            n = n.parentNode
        end
    end

    local function onExtendStatusChange(n)
        if n.imgUp and n.imgDown then
            if not n.isFinal then
                if n.extended then
                    n.imgUp:hide()
                    n.imgDown:show()
                else
                    n.imgUp:show()
                    n.imgDown:hide()
                end
            else
                n.imgUp:hide()
                n.imgDown:hide()
            end
        end
    end

    local GetNode
    local function ExtendList(i)
        i.selected = false
        local l = ccui.Layout:create()
        l:setLayoutType(ccui.LayoutType.VERTICAL)
        l:setContentSize(i:findChild("Panel"):getContentSize())
        i:setContentSize(l:getContentSize())
        l:addChild(i)
        i.realNode = l
        l.getChildren = function()
            if l._children then
               return l._children
            end

            l._children = {}
            l._childrenHeight = 0
            local cs = i._data.children or {}
            for k, v in ipairs(cs) do
                local sub = GetNode(i.ndata.lv + 1, v)
                sub.setData(v)
                sub.parentNode = l

                l:addChild(sub)
                l._childrenHeight = l._childrenHeight + sub:getContentSize().height
                l._children[#l._children + 1] = sub
            end

            return l._children
        end

        l.resetSize = function()
            l._childrenHeight = 0
            for k, v in ipairs(l._children) do
                if v:isVisible() then
                    l._childrenHeight = l._childrenHeight + v:getContentSize().height
                end
            end
            
            l:setContentSize(cc.size(i:getContentSize().width, i:getContentSize().height + l._childrenHeight))

            l.cresetSize()
        end

        l.cresetSize = function()
            if i.parentNode and i.parentNode.resetSize then
                i.parentNode:resetSize()
            end
        end

        l.showChildren = function(b)
            local cs = l.getChildren()
            l._childrenHeight = 0
            for k, v in pairs(cs) do
                v:setVisible(b)
                if v:isVisible() then
                    l._childrenHeight = l._childrenHeight + v:getContentSize().height
                end
            end
        end

        l.colapse = function()
            i.extended = false
            l:setContentSize(i:getContentSize())
            l.showChildren(false)

            l.cresetSize()
            onExtendStatusChange(i)
        end 

        l.extend = function(aAchCfg)
            i.extended = true
            l.showChildren(true)
            l:setContentSize(cc.size(i:getContentSize().width, i:getContentSize().height + l._childrenHeight))

            l.cresetSize()
            onExtendStatusChange(i)
        end

        l.selectItem = function()
            if i.selected then
                l.extend()
            else 
                l.colapse()
            end
        end

        return l
    end

    local function isFinal(d)
        while d.children do
            if #d.children > 1 then
                return false
            end
            d = d.children[1]
        end
        return true
    end

    local function finalData(d)
        while d and d.children do
            d = d.children[1]
        end
        return d
    end

    GetNode = function(lv, data)
        local t = tnodes[lv]
        local n = t.node:clone()
        n.realNode = n
        n.selected = false
        n.extended = false
        n.isFinal = isFinal(data)
        n.ndata = {lv=lv}
        n.panel = n:findChild("Panel")
        n:setContentSize(n.panel:getContentSize())
        -- n.panel:setBackGroundColorType(ccui.LayoutBackGroundColorType.none)
        n.lblName = n:findChild("Panel/name")
        n.btnSelect = n:findChild("Panel/selected_btn")
        n.btnSelect:setPressedActionEnabled(false)
        n.lblName:setTextColor(self.idlColor)

        n.imgUp = n:findChild("Panel/img_2")
        n.imgDown = n:findChild("Panel/img_1")

        if tnodes[lv + 1] then
            if not n.isFinal then
                ExtendList(n)
            end
        end
        
        onExtendStatusChange(n)

        n.select = function()
            n.check(true)
            if n.isFinal then
                ccall(tnodes[#tnodes].onSelect, nil, finalData(data), n.selected)
            else
                if n.realNode.selectItem then
                    n.realNode.selectItem()
                    n.realNode._children[1].select()
                end
                ccall(t.onSelect, n, n._data, n.selected)
            end
            checkLastBtn(n)
        end

        n.btnSelect:addClickEventListener(function()
            n.select()
        end)

        n.panel:addClickEventListener(function()
            if n.extended then
                ccall(n.realNode.colapse)
            else
                ccall(n.realNode.extend)
            end
        end)

        n.setData = function(data)
            n._data = data

            ccall(t.initNode, n, data)
            self.nodes[data.ID] = n
            ccall(n.realNode.colapse)
        end

        n.check = function(aCheck)
            if aCheck == nil then
                n.selected = not n.selected
            else
                n.selected = aCheck
            end

            n.btnSelect:setTouchEnabled(not n.selected)
            n.btnSelect:setBright(not n.selected)
            if n.selected then
                n.lblName:setTextColor(self.selColor)
            else
                n.lblName:setTextColor(self.idlColor)
            end
        end

        n.checkAndColapse = function(aCheck)
            n.check(aCheck)
            if not aCheck then
                ccall(n.realNode.colapse)
            end
        end

        return n
    end

    self.resetSize = function()
        self.typeTree:requestRefreshView()
        self.typeTree:forceDoLayout()
    end
  
    self.refreshData = function(self, treeData)
        self.treeData = treeData
        self.typeTree:removeAllChildren()
        self.nodes = {}
        for k, v in ipairs(treeData.children) do
            local i = GetNode(1, v)
            i.setData(v)
            i.parentNode = self
            self.typeTree:pushBackCustomItem(i.realNode)
        end
    end

    self.selectNode = function(self, aId)
        local d = self.treeData[tostring(aId)]
        local nodes = {}
        if d then
            while d do
                local n = self.nodes[tostring(d.ID)]
                if n then
                    table.insert(nodes, 1, n)
                end
                d = d.p
            end
        else
            d = self.treeData
            while d.children and d.children[1] do
                local n = self.nodes[tostring(d.children[1].ID)]
                table.insert(nodes, n)

                d = d.children[1]
            end
        end
        
        for i, v in ipairs(nodes) do
            v:select()
        end
    end

    if param and param.root and param.root.children then
        self:refreshData(param.root)
    end
    return self
end

return UIUtil